﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace BacteriaSimulation.Simulation
{
    public class IndexGrid
    {
        public IndexGridCell[,] Cells { get; set; }
        //public IndexGridCell OverflowCell;

        protected int rowCount;
        protected int columnCount;
        public SimulationEnvironment Env { get; set; }

        public int RowCount
        {
            get
            { return rowCount; }
        }
        public int ColumnCount
        {
            get
            {
                return columnCount;
            }
        }

        public IndexGrid(SimulationEnvironment env, int rowCount, int columnCount)
        {
            this.Env = env;
            this.rowCount = rowCount;
            this.columnCount = columnCount;

            this.Cells = new IndexGridCell[RowCount, ColumnCount];

            for (int rowIndex = 0; rowIndex < this.RowCount; rowIndex++)
            {
                for (int columnIndex = 0; columnIndex < this.ColumnCount; columnIndex++)
                {
                    Cells[rowIndex, columnIndex] = new IndexGridCell(rowIndex, columnIndex);
                }
            }

            //this.OverflowCell = new IndexGridCell(-1, -1);
        }

        public void Assign(Bacterium bacterium)
        {
            int rowIndex = -1;
            int columIndex = -1;
            try
            {
                double x = bacterium.X;
                double y = bacterium.Y;

                //if (x > Env.Width)
                //{
                //    System.Diagnostics.Debug.WriteLine("X ( = " + bacterium.X + ") exceeds environment width for bacterium");
                //}
                //if (y > Env.Height)
                //{
                //    System.Diagnostics.Debug.WriteLine("Y ( = " + bacterium.Y + ") exceeds environment height for bacterium");
                //}

                double cellWidth = Env.Width / columnCount;
                double cellHeight = Env.Height / rowCount;

                columIndex = (int)Math.Floor(x / cellWidth);
                rowIndex = (int)Math.Floor(y / cellHeight);

                IndexGridCell cell = this.Cells[rowIndex, columIndex];
                if (cell != bacterium.Cell)
                {
                    this.Remove(bacterium);
                }

                cell.AddBacterium(bacterium);
            }
            catch (Exception)
            { 
                System.Diagnostics.Debug.WriteLine("rowIndex = "+ rowIndex + " - columnIndex = " + columIndex + "; Bacterium = " + bacterium.Strategy.GetType().Name);
            }
        }

        public void Remove(Bacterium toRemove)
        {
            if (toRemove.Cell != null)
            {
                toRemove.Cell.RemoveBacterium(toRemove);
            }
        }

        public List<IndexGridCell> GetAdjacentCells(int rowIndex, int columnIndex)
        {
            List<IndexGridCell> adjacent = new List<IndexGridCell>(4);
            if(rowIndex + 1 < RowCount)
            {
                adjacent.Add(Cells[rowIndex + 1, columnIndex]);
            }
            if(rowIndex - 1 >= 0)
            {
                adjacent.Add(Cells[rowIndex - 1, columnIndex]);
            }
            if(columnIndex + 1 < ColumnCount)
            {
                adjacent.Add(Cells[rowIndex, columnIndex + 1]);
            }
            if(columnIndex - 1 >= 0)
            {
                adjacent.Add(Cells[rowIndex, columnIndex - 1]);
            }

            return adjacent;
        }
    }
}
